<?php

namespace App\Jobs;

use App\Http\Controllers\SmallPay;
use App\Http\Controllers\SmallPayV3;
use App\Models\AnswerActivity;
use App\Models\AnswerActivityPacketTransfer;
use App\Models\AnswerActivityUserGift;
use App\Models\UserWechatInfo;
use Illuminate\Bus\Queueable;
use Illuminate\Contracts\Queue\ShouldBeUnique;
use Illuminate\Contracts\Queue\ShouldQueue;
use Illuminate\Foundation\Bus\Dispatchable;
use Illuminate\Queue\InteractsWithQueue;
use Illuminate\Queue\SerializesModels;
use Illuminate\Support\Facades\Log;

/**
 * 答题活动红包转账队列（新版本商家付款到零钱）
 */
class AnswerActivityTransferJob implements ShouldQueue
{
    use Dispatchable, InteractsWithQueue, Queueable, SerializesModels;


    public $key;
    public $value;

    /**
     * 任务最大尝试次数。
     *
     * @var int
     */
    public $tries = 3;   //这里写了，程序会自动尝试执行
    /**
     * 任务运行的超时时间。
     *
     * @var int
     */
    public $timeout = 180;


    /**
     * Create a new job instance.
     *
     * @return void
     * //执行监听程序（php artisan queue:listen），会自动把之前写入队列的参数拿出，放到对应位置，这里只是个写入对应的程序参数对应，但是他们不是同步执行的
     */
    public function __construct($key = null, $value = null)
    {
        $this->key = $key;
        $this->value = $value;
    }

    /**
     * Execute the job.
    
     *   $value =  $data=[
     *          'act_name'=> $act_name,    //活动名称
     *          'user_gift_id'=> $answer_activity_user_gift_id,   //用户礼物id
     *  ];
     */
    public function handle()
    {
        $answerActivityDrawJob = new AnswerActivityDrawJob();
        if ($this->key != $answerActivityDrawJob->answer_red_transfer_key) {
            return false; //不是当前类型，不处理
        }
        
        $answerActivityUserGiftModel = new AnswerActivityUserGift();
        $answerActivityUserGiftInfo = $answerActivityUserGiftModel->where('id', $this->value['user_gift_id'])->first();
        if (empty($answerActivityUserGiftInfo) || $answerActivityUserGiftInfo->type != 1 || $answerActivityUserGiftInfo->state != 1 || empty($answerActivityUserGiftInfo->price)) {
            return false; //不是红包或已发放，不处理
        }
        //正常转账流程
        $user_guid = $answerActivityUserGiftInfo->user_guid;
        $order_id = $answerActivityUserGiftInfo->order_id;
        $packet_msg = $this->value['act_name'];
        $price = $answerActivityUserGiftInfo->price * 100;

        //  $price = 0.3 * 100; //TODO测试使用

        //体验用户不发红包
        $act_info = AnswerActivity::where('id', $answerActivityUserGiftInfo->act_id)->where('is_del', 1)->first();
        if (
            $act_info['start_time'] > date('Y-m-d H:i:s') &&
            !in_array(
                $answerActivityUserGiftInfo->user_guid,
                [
                 //   'e01452dc7ad3300aa43e1e88fbd91c5f', //15102892664
                 //   '559bf2d43bb0394ede9f16302ac9158b', //18081838416
                ]
            )
        ) {
            Log::channel('handcmdlog')->info("活动未开始,不能发送红包" . $user_guid);
            return false;
        }

        $userWechatModel = new UserWechatInfo();
        $wechat_user_info = $userWechatModel->where('user_guid', $user_guid)->where('node', 'YXYZ')->first();

        if (empty($wechat_user_info)) {
            Log::channel('handcmdlog')->info("用户获取失败,不能转账：" . $user_guid);
            return false;
        }

        //进行转账操作，写入正在转账中
        $answerActivityUserGiftModel->where('order_id', $order_id)->update(['pay_time' => date('Y-m-d H:i:s'), 'state' => 8]); //这里 8 是发放红包中
        $smallPayModel = new SmallPayV3();

        $res = $smallPayModel->wechatTransfer($order_id, $price, $wechat_user_info['open_id'], '竞答活动红包', $packet_msg);
        if ($res !== true) {
            Log::channel('handcmdlog')->info("转账失败,理由为" . $res . ",竞答活动用户获奖数据id：" . $this->value['user_gift_id'] . ';订单号为：' . $order_id);

            $answerActivityUserGiftModel->where('order_id', $order_id)->update(['pay_time' => date('Y-m-d H:i:s'), 'state' => 1, 'fail_reason' => $res]); // 改为 1 ，未发放，不影响之前逻辑
        }
        //后面就不处理了，正在转账中了
    }

    //转账失败
    public function failed()
    {
        Log::channel('handcmdlog')->info('答题红包转账失败');

        dump('failed'); //程序报错才会走这里，try cache 拦截后，不会走这里，程序会以执行成功处理
    }
}
